package com.dasberg.gwt.server;

import com.dasberg.guice.InjectDependencies;
import com.dasberg.gwt.client.AuthenticationException;
import com.dasberg.gwt.client.AuthenticationService;
import com.dasberg.gwt.client.AuthenticationToken;
import com.dasberg.gwt.domain.IToken;
import com.dasberg.gwt.domain.IUser;
import com.google.gwt.user.server.rpc.RemoteServiceServlet;
import com.google.inject.Inject;
import org.apache.log4j.Logger;

/**
 * The Actual Authentication implementation.
 * @author mischa
 */
public class AuthenticationAdapter extends RemoteServiceServlet implements AuthenticationService {
    private static final Logger LOG = Logger.getLogger(AuthenticationAdapter.class);

    @Inject
    private AuthenticationProvider provider;

    @InjectDependencies
    public AuthenticationAdapter() {
    }

    /** {@inheritDoc}. */
    public boolean authenticate(String username, String password) {
        try {
            IToken token = provider.authenticate(username, password);
            IUser user = token.getUser();
            setAuthenticationToken(new AuthenticationToken(token.getUuid().toString(), user.getUsername(), getFullName(token.getUser())));
            return true;
        } catch (AuthenticationException e) {
            return false;
        }
    }

    /** {@inheritDoc}. */
    public void deauthenticate() {
        provider.deauthenticate(getAuthenticationToken());
        setAuthenticationToken(null);
    }

    /** {@inheritDoc}. */
    public boolean isInRole(String role) {
        return provider.isUserInRole(getAuthenticationToken(), role);
    }

    /** {@inheritDoc}. */
    public boolean isAuthenticated() {
        return provider.isTokenValid(getAuthenticationToken());
    }

    /** {@inheritDoc}. */
    public String getAuthenticatedUser() {
        AuthenticationToken authenticationToken = getAuthenticationToken();
        return authenticationToken!= null ? authenticationToken.getDisplayname() : null;
    }

    /**
     * Gets the authenticationtoken on the session.
     * @return token The AuthenticationToken.
     */
    private AuthenticationToken getAuthenticationToken() {
        return (AuthenticationToken) this.getThreadLocalRequest().getSession().getAttribute("authenticationToken");
    }

     /**
     * Sets the authenticationtoken on the session.
     * @param token The AuthenticationToken.
     */
    private void setAuthenticationToken(AuthenticationToken token) {
        this.getThreadLocalRequest().getSession().setAttribute("authenticationToken", token);
    }

    /**
     * Gets the full name.
     * @param user The user.
     * @return fullName The full name.
     */
    private String getFullName(IUser user) {
        String fullName = "";
        if (user.getFirstName() != null) {
            fullName += user.getFirstName();
        }
        if (user.getLastName() != null) {
            fullName += " " + user.getLastName();
        }
        return fullName.trim();
    }
}